package com.gridmobi.xrtb.routers.bidding;


import com.alibaba.fastjson.JSONObject;
import com.gridmobi.xrtb.domain.dsp.DspTrackLog;
import com.gridmobi.xrtb.domain.dsp.common.AppConstant;
import com.gridmobi.xrtb.domain.dsp.common.enums.ExchangesE;
import com.gridmobi.xrtb.dspcounter.DspCounterHandler;
import com.gridmobi.xrtb.handler.monitor.RtbStatus;
import com.gridmobi.xrtb.handler.monitor.SimpleData;
import com.gridmobi.xrtb.model.rtb.MacrosTemplate;
import com.gridmobi.xrtb.util.RtbUtil;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.lang3.StringUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;
import org.springframework.web.bind.annotation.RequestParam;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.time.LocalDateTime;
import java.util.Map;
import java.util.concurrent.atomic.AtomicInteger;

@Controller
@RequestMapping("/")
//@Slf4j
public class AlgorixTrackingController {
    private static final Logger impLog = LoggerFactory.getLogger("impLog");
    private static final Logger clickLog = LoggerFactory.getLogger("clickLog");
    private static final Logger errorLog = LoggerFactory.getLogger("errorLog");
    private static final Logger bizLog = LoggerFactory.getLogger("bizLog");

    @Autowired
    DspCounterHandler dspCounterHandler;
    private double defaultPrice = 5.0;
    private AtomicInteger errorcounter = new AtomicInteger();

    @GetMapping("tracking")
    public void tracking(@RequestParam Map<String, String> args, HttpServletRequest request, HttpServletResponse response) throws Exception {

        String type = request.getParameter("type");
        if (StringUtils.isBlank(type)) {
            return;
        }
        String query = request.getQueryString();
        if (type.equals("clicktrackers")){
             clickLog.info(query);
             click(args, request, response);
         }else if (type.equals("imptrackers")){
             impLog.info(query);
             imp(args, request, response);
             count(args, request, response);
        } else {
             bizLog.info("tracking param = {}", query);
         }

    }

    public void count(Map<String, String> args, HttpServletRequest request, HttpServletResponse response) {

        try {
            LocalDateTime now = LocalDateTime.now();
            DspTrackLog trackArgs = null;
            String bidid = args.get("bidid");


            if (bidid != null) {
                trackArgs = RtbUtil.packTrackArgs(now, args, request);
                if (trackArgs.getCid() == null) {
                    trackArgs.setCid(request.getParameter("cid"));
                }
                dspCounterHandler.countWin(Integer.parseInt(trackArgs.getCid()), trackArgs.getCrid(), trackArgs.getGeo(), trackArgs.getAppid(), trackArgs.getOs(), ExchangesE.getCode(trackArgs.getChannel()));
                /*
                default cpm
                 */
                double price = 0f;
                try {
                    price = Double.parseDouble(trackArgs.getPrice());
                } catch (Exception e) {

                    trackArgs.setPrice(String.valueOf(defaultPrice));
                    price = defaultPrice;
                }

                double actprice = price / 1000;

                dspCounterHandler.countCosts(Integer.parseInt(trackArgs.getCid()), trackArgs.getCrid(), trackArgs.getGeo(), trackArgs.getAppid(), trackArgs.getOs(), actprice, ExchangesE.getCode(trackArgs.getChannel()));

            }

        } catch (Exception e) {
            errorLog.error("WINERROR", e);
            int i = errorcounter.incrementAndGet();
            if (i % 10 == 0) {
                RtbStatus.BID_LOCK_BY_WINNOTICE_ERROR = true;
            }
        }
    }

    public void imp( Map<String, String> args, HttpServletRequest request, HttpServletResponse response) {
        LocalDateTime now = LocalDateTime.now();
        DspTrackLog trackArgs = RtbUtil.packTrackArgs(now, args, request);
        /*记录Imp*/
        if (trackArgs.getCid() == null) {
            trackArgs.setCid(request.getParameter("cid"));
        }
        dspCounterHandler.countImpr(Integer.parseInt(trackArgs.getCid()), trackArgs.getCrid(), trackArgs.getGeo(), trackArgs.getAppid(), trackArgs.getOs(), ExchangesE.getCode(trackArgs.getChannel()));
    }

    public void click( Map<String, String> args, HttpServletRequest request, HttpServletResponse response) {
        String trackurl = null;
        try {
            LocalDateTime now = LocalDateTime.now();
            DspTrackLog trackArgs = RtbUtil.packTrackArgs(now, args, request);
            if (trackArgs.getCid() == null) {
                trackArgs.setCid(request.getParameter("cid"));
            }

            StringBuilder click = new StringBuilder("DSP");
            if (StringUtils.isNotBlank(trackArgs.getBidId())) {
                click.append(trackArgs.getCid() == null ? "" : trackArgs.getCid())
                        .append(AppConstant.URL_SEPARATOR)
                        .append(trackArgs.getCrid() == null ? "" : trackArgs.getCrid())
                        .append(AppConstant.URL_SEPARATOR)
                        .append(StringUtils.isBlank(trackArgs.getBidstmp()) ? System.currentTimeMillis() : trackArgs.getBidstmp());
                String clickId = click.toString();

                trackurl = SimpleData.CAMPAIGNS_LANDURL.get(trackArgs.getCid());

                trackurl = MacrosTemplate.replaceTrackurl(trackurl, trackArgs, clickId);
                trackArgs.setClickid(clickId);


            } else {

                bizLog.warn("Click Track Bidid is null :".concat(JSONObject.toJSONString(trackArgs)));
            }
            /*记录点击*/
            dspCounterHandler.countClicks(Integer.parseInt(trackArgs.getCid()), trackArgs.getCrid(), trackArgs.getGeo(), trackArgs.getAppid(), trackArgs.getOs(), ExchangesE.getCode(trackArgs.getChannel()));

            args.put("trackurl", trackurl);


        } catch (Exception e) {
            e.printStackTrace();
            bizLog.error("trackerror:".concat(JSONObject.toJSONString(args)), e);
        }
        bizLog.warn(JSONObject.toJSONString(args));

    }
}
